package com.app.service.impl;

import cn.hutool.captcha.CaptchaUtil;
import cn.hutool.captcha.LineCaptcha;
import com.app.pojo.LoginState;
import com.app.pojo.Status;
import com.bby.Settings;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.HashMap;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;

@Service
public class CaptchaService {
    HashMap<String, LineCaptcha> captchas=new HashMap<>();
    HashMap<String, Long> creatTimes=new HashMap<>();
    ScheduledExecutorService scheduledExecutorService = Executors.newScheduledThreadPool(10);
    void timeoutChecksTask(String id,Long creatTime){
        scheduledExecutorService.schedule(new Thread(()->{
            Long outTime = creatTimes.get(id);
            System.out.println("清除验证码："+id);
            if (outTime==null|| !outTime.equals(creatTime)) return;
            //超时，清除
            creatTimes.remove(id);
            captchas.remove(id);
        }),Settings.captchaValidSeconds, TimeUnit.SECONDS);
    }
    public LineCaptcha getCaptchaById(String id){
        LineCaptcha captcha=captchas.get(id);
        if (captcha==null) captcha = CaptchaUtil.createLineCaptcha(Settings.captchaWidth,Settings.captchaHigh);
        else captcha.createCode();//重新生成

        Long creatTime=new Date().getTime();
        creatTimes.put(id,creatTime);
        captchas.put(id,captcha);
        timeoutChecksTask(id,creatTime);//设置定时删除任务
        System.out.println(id+" 获取新验证码："+captcha.getCode());
        return captcha;
    }

    /**
     * 检验验证码，不管通不通过，检验完成后验证码都会清除
     * @param id session ID
     * @param inputCode 用户输入的验证码
     * @return 0：通过，1：不通过，2：验证码失效
     */
    public int verifyCaptcha(String id,String inputCode){
        System.out.println(id+" 验证："+inputCode);
        LineCaptcha captcha = captchas.get(id);
        if (captcha == null) return Status.CAPTCHA_OUT_TIME;// 超时

        creatTimes.remove(id);
        captchas.remove(id);
        return captcha.verify(inputCode)? Status.SUCCESS:Status.FAIL;
    }
}
